package test;


import sun.reflect.generics.reflectiveObjects.ParameterizedTypeImpl;

import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.lang.reflect.TypeVariable;

public class GenericTest3<T> {

    private Class<T> clazz;

    public T getDemo() throws InstantiationException, IllegalAccessException {
        Class c = getClass();
        TypeVariable[] typeParameters = c.getTypeParameters();
        System.out.println(typeParameters); //[ T ]

        Type genericSuperclass = c.getGenericSuperclass(); // Object
        return null;
    }

    public static void test() throws InstantiationException, IllegalAccessException {
        String str = new GenericTest3<String>().getDemo();
    }

    public static void main(String[] args) throws IllegalAccessException, InstantiationException {
        new GenericTest3_1<String>();
        new GenericTest3_2();
        test();
    }


    static class GenericTest3_1<T> extends GenericTest3<T> {
        public GenericTest3_1() {
            Type type = getClass().getGenericSuperclass(); // ParameterizedTypeImpl test.GenericTest3<T>
            Type type2 = ((ParameterizedType) type).getActualTypeArguments()[0]; // TypeVariable
            System.out.println();
        }
    }

    /**
     * 只有在声明的时候指定了T的具体类型,代码里才可以获取具体的类型.不然T的类型是不能再运行期间获取
     */
    static class GenericTest3_2 extends GenericTest3<Integer> {
        public GenericTest3_2() {
            Type type = getClass().getGenericSuperclass(); // ParameterizedTypeImpl test.GenericTest3<Integer>
            Class<?> rawType = ((ParameterizedTypeImpl) type).getRawType(); // Class GenericTest3
            Type type2 = ((ParameterizedType) type).getActualTypeArguments()[0]; // Class Integer
            System.out.println();
        }
    }
}